package service

import (
	"encoding/json"
	"fmt"
	"multimedia/utils"
	"net/http"
	"strconv"
	"strings"
	"time"

	"github.com/gin-gonic/gin"
	"github.com/gin-gonic/gin/binding"
	log "github.com/sirupsen/logrus"
)

func (s *Srv) MediaCallBack(c *gin.Context) {
	appId := c.Param("appId")
	meetId := c.Param("meetId")
	evtData := utils.EvtDataReq{}
	rsp := utils.EvtDataRes{
		EvtCallbackUrl:    fmt.Sprintf("/management/apps/%s/meetings/%s/evt", appId, meetId),
		CallbackArg:       "",
		CallbackTimeoutMs: 180000,
	}
	msg, _ := json.Marshal(rsp)
	c.JSON(http.StatusOK, msg)
	if err := c.ShouldBindBodyWith(&evtData, binding.JSON); err != nil {
		log.WithField("Func", "MediaCallBack").Warnf(" the err is:%v", err)
		c.JSON(http.StatusBadRequest, gin.H{"code": -1, "msg": err.Error()})
		return
	}
	id, _ := strconv.ParseInt(appId, 10, 64)
	err, roomInfo := s.mysql.GetRoomInfoByAppIdAndMeetId(id, meetId)
	if err != nil {
		log.WithField("Func", "MediaCallBack").Warnf("room not find %s,%s,%d,%v", evtData.EvtType, meetId, id, err)
		return
	}
	timestamp := evtData.EvtTimeStamp
	if timestamp == 0 {
		timestamp = time.Now().UnixMilli()
	}
	s.mysql.InsertRtcEvent(&roomInfo, &evtData)
	switch evtData.EvtType {
	case "CRT":
		confrId := evtData.ConferId
		s.mysql.UpdateRoomInfoStatus(roomInfo.Id, utils.CREATED, timestamp, confrId)
		log.WithField("Func", "MediaCallBack").Warnf("Create meeting %d the roomid is:%d", roomInfo.Id, roomInfo.RoomId)
	case "ENTER":
		s.mysql.InsertRoomPlayUser(&roomInfo, &evtData, timestamp)
		log.WithField("Func", "MediaCallBack").Warnf("enter meeting %d the roomid is:%d the member is:%s",
			roomInfo.Id, roomInfo.RoomId, evtData.MemName)
	case "EXIT":
		s.mysql.UpdateUserExitRoomPlayTime(roomInfo.Id, evtData.MemName, timestamp)
		log.WithField("Func", "MediaCallBack").Warnf("exit meeting %d the roomid is:%d the member is:%s",
			roomInfo.Id, roomInfo.RoomId, evtData.MemName)
	case "CONFR_CLOSE":
		roomInfoId := roomInfo.Id
		s.mysql.CloseRoom(roomInfoId, utils.TERMINATED, timestamp)
		log.WithField("Func", "MediaCallBack").Warnf("close meeting %d the roomid is:%s", roomInfoId, roomInfo.RoomId)
		s.wsClient.NotifyRecEnded(roomInfo.Id, roomInfo.RoomId)
	case "PLAY_BACK":
		playUrl := evtData.PlayURL
		if !strings.HasSuffix(playUrl, ".json") && !strings.HasSuffix(playUrl, ".ffprobe") {
			s.mysql.UpdateRecord(roomInfo.Id, playUrl, evtData.MemName, roomInfo.Record)
			log.WithField("Func", "MediaCallBack").Warnf("playback meeting the roomInfoId is:%d the url is:%s", roomInfo.Id, playUrl)
			log.WithField("Func", "MediaCallBack").Warnf("the meeting MemName is: %s, room id is: %s", evtData.MemName, roomInfo.RoomId)
			s.wsClient.NotifyRecEnded(roomInfo.Id, roomInfo.RoomId)
		}
	}
}
